﻿#ifndef _DATA_RECEIVER_
#define _DATA_RECEIVER_

#include <chrono>
#include <iostream>
#include <thread>
#include <zhelpers.hpp>
#include <zmq.hpp>

#include "DataRingBuf.h"
#include "SensorData.pb.h"
#include "util.h"

// 集采数据接收端（作为zmq数据通信的服务端）
class DataReceiver
{
public:
    DataReceiver(std::string send_port, std::string recv_port)
        : sampling_(true), context_(1), push_sock_(context_, ZMQ_PUSH), pull_sock_(context_, ZMQ_PULL), record_(false)
    {
        // 获取当前系统时间并转为字符串
        auto current_time = std::chrono::system_clock::to_time_t(std::chrono::system_clock::now());
        std::tm local_time;
        localtime_s(&local_time, &current_time);
        std::stringstream ss;
        ss << std::put_time(&local_time, "%Y-%m-%d_%H-%M");
        // 从字符串流中获取字符串
        std::string log_path = "logs/log-data_receiver_" + ss.str() + ".txt";

        logfile_recv_ = LOG_FILE("DataReceiver", log_path);
        message_queue_freqA_ = new DataRingBuf<TotalMessage>(KBufSize);
        message_queue_freqB_ = new DataRingBuf<TotalMessage>(KBufSize);
        message_queue_freqC_ = new DataRingBuf<TotalMessage>(KBufSize);
        std::string push_url = "tcp://*:" + send_port;
        std::string pull_url = "tcp://*:" + recv_port;

        try {
            push_sock_.bind(push_url);
            pull_sock_.bind(pull_url);
        } catch (zmq::error_t &e) {
            LOG_ERROR("DataReceiver zmq bind fail:%s", e.what());
        }

        thread_recv_ = std::thread([this]() { taskRecv(); });
    }

    bool startSampling(const int &freqa, const int &freqb, const int &freqc, const int &sensors_num,
                       const bool &record);
    bool stopSampling();
    bool handlData(TotalMessage &&total_message, const TotalMessage::FreqType &freq_type);

    ~DataReceiver() { stopTask(); }

private:
    void taskRecv();
    void stopTask();

private:
    std::thread thread_recv_; // 取数据线程

    zmq::context_t context_;
    zmq::socket_t push_sock_; // 发送指令，如：开始采集、停止采集
    zmq::socket_t pull_sock_; // 接收采集数据
    bool sampling_;           // 采样线程运行标识
    bool record_;             // 是否录制

    DataRingBuf<TotalMessage> *message_queue_freqA_;
    DataRingBuf<TotalMessage> *message_queue_freqB_;
    DataRingBuf<TotalMessage> *message_queue_freqC_;

    std::shared_ptr<spdlog::logger> logfile_recv_; // 日志文件对象
};
#endif //_DATA_RECEIVER_